package org.springblade.ocpp.send;

import cn.hutool.core.codec.Base64;
import cn.hutool.core.thread.ThreadUtil;
import cn.hutool.core.util.IdUtil;
import com.alibaba.fastjson2.JSONObject;
import lombok.extern.slf4j.Slf4j;
import org.springblade.ocpp.domain.req.DataTransferRequest;
import org.springblade.ocpp.domain.req.RemoteStartTransactionRequest;
import org.springblade.ocpp.domain.req.RemoteStopTransactionRequest;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.DelayQueue;
import java.util.concurrent.Delayed;

/**
 * @author lhb
 * @date 2024/10/5 下午3:24
 */
@Slf4j
public class DelaySend {

	private static final DelayQueue<Delayed> DELAY_QUEUE = new DelayQueue<>();

	public static void put(Delayed delayed) {
		DELAY_QUEUE.add(delayed);
	}

	public static void start() {
		ThreadUtil.newSingleExecutor().execute(() -> {
			while (true) {
				try {
					Delayed task = DELAY_QUEUE.take();
					log.info("OCPP Delayed queue data:{}", JSONObject.toJSONString(task));
					if (task instanceof RemoteStartTransactionRequest) {
						// 发送远程开始充电消息
						RemoteStartTransactionSend.send((RemoteStartTransactionRequest) task);
					} else if (task instanceof DataTransferRequest) {
						// 发送资料给充电桩
						DataTransferSend.send((DataTransferRequest) task);
					} else if (task instanceof RemoteStopTransactionRequest) {
						RemoteStopTransactionSend.send((RemoteStopTransactionRequest) task);
					} else {
						log.warn("延迟队列未匹配到具体类型");
					}
				} catch (Exception e) {
					log.error(e.getMessage(), e);
				}
			}
		});
	}

	public static void main(String[] args) {
		DelaySend.start();

		// 准备发送 RemoteStartTransaction 信息给充电桩准备开始充电
		RemoteStartTransactionRequest delay = new RemoteStartTransactionRequest(1);
		delay.setSid("device_1001");
		delay.setConnectorId(1);
		delay.setIdTag(IdUtil.fastSimpleUUID());
		RemoteStartTransactionRequest.ChargingProfileDTO chargingProfile = new RemoteStartTransactionRequest.ChargingProfileDTO();
		chargingProfile.setChargeProfileId(1);
		chargingProfile.setChargingProfileKind("Relative");
		chargingProfile.setChargingProfilePurpose("TxProfile");
		RemoteStartTransactionRequest.ChargingProfileDTO.ChargingScheduleDTO chargingSchedule = new RemoteStartTransactionRequest.ChargingProfileDTO.ChargingScheduleDTO();
		chargingSchedule.setChargingRateUnit("A");
		List<RemoteStartTransactionRequest.ChargingProfileDTO.ChargingScheduleDTO.ChargingSchedulePeriodDTO> chargingSchedulePeriod = new ArrayList<>();
		RemoteStartTransactionRequest.ChargingProfileDTO.ChargingScheduleDTO.ChargingSchedulePeriodDTO chargingSchedulePeriodDTO = new RemoteStartTransactionRequest.ChargingProfileDTO.ChargingScheduleDTO.ChargingSchedulePeriodDTO();
		chargingSchedulePeriodDTO.setLimit(60);
		chargingSchedulePeriodDTO.setStartPeriod(0);
		chargingSchedulePeriod.add(chargingSchedulePeriodDTO);
		chargingSchedule.setChargingSchedulePeriod(chargingSchedulePeriod);
		chargingProfile.setChargingSchedule(chargingSchedule);
		delay.setChargingProfile(chargingProfile);
		// 设置到延时队列, 延迟后发送消息到充电桩
		DelaySend.put(delay);

		// 发送充电站资料给客户端
		DataTransferRequest dataTransferRequest = new DataTransferRequest(2);
		dataTransferRequest.setSid("device_1001");
		dataTransferRequest.setVendorId("Spiro");
		dataTransferRequest.setMessageId("ChargingProfile");

		JSONObject data = new JSONObject();
		data.put("chargingProfileId", 1);
		data.put("connectorId", 1);
		data.put("TargetSOC", 100);
		data.put("format", "Raw");
		data.put("unit", "percent");
		dataTransferRequest.setData(Base64.encode(data.toString()));

		DelaySend.put(dataTransferRequest);
	}

}
